package ai4games_tests.soccer;

import game2dai.World;
import game2dai.entities.BaseEntity;
import game2dai.fsm.State;
import game2dai.fsm.Telegram;
import game2dai.maths.FastMath;
import game2dai.steering.SBF;

public class PlayerReceiveBall extends State implements Constants {


	private static PlayerReceiveBall instance = null;

	public static PlayerReceiveBall state(){
		if(instance == null){
			instance = new PlayerReceiveBall();
			instance.name = "Receive ball";
		}
		return instance;
	}

	@Override
	public void enter(BaseEntity owner) {
		PlayerBase player = (PlayerBase) owner;
		player.team.setReceivingPlayer(player);
		player.team.setControllingPlayer(player);

		// There are two types of receive behaviour. One uses arrive to direct
		// the receiver to the position sent by the passer in its telegram. The
		// other uses the pursuit behavior to pursue the ball. 
		// This statement selects between them dependent on the probability
		// ChanceOfUsingArriveTypeReceiveBehavior, whether or not an opposing
		// player is close to the receiving player, and whether or not the receiving
		// player is in the opponents 'hot region' (the third of the pitch closest
		// to the opponent's goal
		if(player.isInHotRegion() || 
				Math.random() < ChanceOfUsingArriveTypeReceiveBehavior &&
				!player.team.isOpponentWithinRadius(player.pos(), PassThreatDistance)){
			player.AP().arriveOn(player.targetPos, SBF.FAST);
		}
		else {
			player.AP().pursuitOn( player.team.pitch.ball);
		}
	}

	@Override
	public void execute(BaseEntity owner, double deltaTime, World world) {
		PlayerBase player = (PlayerBase) owner;

		// If the player is close enough to the ball or his team loses control
		// then chase ball
		if(player.isBallWithinReceivingRange() || !player.team.isInControl()){
			player.FSM().changeState(PlayerChaseBall.state());
		}

		if(player.isAtTarget()){
			player.AP().arriveOff().pursuitOff();
			player.trackBall();
			player.velocity(0, 0);
		}
	}

	@Override
	public void exit(BaseEntity owner) {
		PlayerBase player = (PlayerBase) owner;
		player.AP().arriveOff().pursuitOff();
		player.team.setReceivingPlayer(null);
	}

	@Override
	public boolean onMessage(BaseEntity owner, Telegram tgram) {
		return false;
	}

}
